// -*-mode:c++; coding:utf-8-*-

#ifndef _XBASE_ASYNC_MODULE_STATS_HPP_
#define _XBASE_ASYNC_MODULE_STATS_HPP_

#include <string>
#include <ext/hash_map>

#include <boost/thread/mutex.hpp>

namespace xbase
{

	// fwd declare
	class async_module;

	class async_module_stats
	{
	public:
		struct item
		{
			std::size_t m_total_number; // 总共创建的实例数
			std::size_t m_live_number; // 当前存在的实例数
			// others
		};

		typedef __gnu_cxx::hash_map<const char*, item> info_map;

	public:
		async_module_stats()
			: m_bytes_written(0)
			, m_bytes_read(0)
			, m_packets_written(0)
			, m_packets_read(0) {}

		static
		void enable();

		static
		void disable();

		static
		void construction(const async_module *module);

		static
		void destruction(const async_module *module);

		static
		void print(std::ostream &out);

		static
		void clear();

		static
		void bytes_written(std::size_t bytes) {
			if(s_async_module_stats != NULL)
			{
				boost::mutex::scoped_lock lock(s_async_module_stats->m_mutex);
				s_async_module_stats->m_bytes_written += bytes;
			}
		}

		static
		void bytes_read(std::size_t bytes) {
			if(s_async_module_stats != NULL)
			{
				boost::mutex::scoped_lock lock(s_async_module_stats->m_mutex);
				s_async_module_stats->m_bytes_read += bytes;
			}
		}

		static
		void packets_written(std::size_t count) {
			if(s_async_module_stats != NULL)
			{
				boost::mutex::scoped_lock lock(s_async_module_stats->m_mutex);
				s_async_module_stats->m_packets_written += count;
			}
		}
		
		static
		void packets_read(std::size_t count) {
			if(s_async_module_stats != NULL)
			{
				boost::mutex::scoped_lock lock(s_async_module_stats->m_mutex);
				s_async_module_stats->m_packets_read += count;
			}
		}

	private:
		boost::mutex m_mutex;
		
		info_map m_info;

		std::size_t m_bytes_written;
		std::size_t m_bytes_read;
		
		std::size_t m_packets_written;
		std::size_t m_packets_read;

		static async_module_stats *s_async_module_stats;
	};

} // namespace xbase

#endif	// _XBASE_ASYNC_MODULE_STATS_HPP_
